package com.webex.ta.hydra.gui.wm;

import javax.swing.*;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicGraphicsUtils;
import javax.swing.plaf.metal.MetalToggleButtonUI;
import java.awt.*;
import java.awt.geom.AffineTransform;

/**
 * Created by Cisco WebEx.
 * User: vegaz
 * Date: 2010-10-19
 * Time: 14:38:06
 */
public class SideBarButtonUI extends MetalToggleButtonUI {
    private static final SideBarButtonUI instance = new SideBarButtonUI();

    private static final Rectangle iconRect = new Rectangle();
    private static final Rectangle textRect = new Rectangle();
    private static final Rectangle viewRect = new Rectangle();
    private static Insets viewInsets = new Insets(0, 0, 0, 0);

    private SideBarButtonUI() {
    }

    public static ComponentUI createUI(JComponent b) {
        return instance;
    }

    public Dimension getPreferredSize(final JComponent c) {
        final SideBarButton button = (SideBarButton) c;
        final Dimension d = super.getPreferredSize(button);

        d.width = (int) (4 + d.width * 1.1f);
        d.height += 4;

        int anchor = button.getAnchor();
        if (anchor == SwingConstants.LEFT || anchor == SwingConstants.RIGHT)
            return new Dimension(d.height, d.width);
        return d;
    }

    public void paint(final Graphics g, final JComponent c) {
        final SideBarButton button = (SideBarButton) c;

        final String text = button.getText();
        final Icon icon = button.isEnabled() ? button.getIcon() : button.getDisabledIcon();

        if (icon == null && text == null)
            return;

        final FontMetrics fm = button.getFontMetrics(button.getFont());
        viewInsets = c.getInsets(viewInsets);

        viewRect.x = viewInsets.left;
        viewRect.y = viewInsets.top;

        int anchor = button.getAnchor();

        if (SwingConstants.LEFT == anchor || SwingConstants.RIGHT == anchor) {
            viewRect.height = c.getWidth() - (viewInsets.left + viewInsets.right);
            viewRect.width = c.getHeight() - (viewInsets.top + viewInsets.bottom);
        } else {
            viewRect.height = c.getHeight() - (viewInsets.left + viewInsets.right);
            viewRect.width = c.getWidth() - (viewInsets.top + viewInsets.bottom);
        }

        iconRect.x = iconRect.y = iconRect.width = iconRect.height = 0;
        textRect.x = textRect.y = textRect.width = textRect.height = 0;

        final String clippedText = SwingUtilities.layoutCompoundLabel(
                c, fm, text, icon,
                button.getVerticalAlignment(), button.getHorizontalAlignment(),
                button.getVerticalTextPosition(), button.getHorizontalTextPosition(),
                viewRect, iconRect, textRect,
                button.getText() == null ? 0 : button.getIconTextGap()
        );

        // Paint button's background

        final Graphics2D g2 = (Graphics2D) g;
        g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
        g2.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);

        final ButtonModel model = button.getModel();

        final Color background = button.getBackground();

        boolean toFill = true;
        boolean toBorder = true;

        if (model.isArmed() && model.isPressed() || model.isSelected()) {
            final Graphics2D g2d = (Graphics2D) g;
            final GradientPaint paint;

            if (anchor == SwingConstants.TOP || anchor == SwingConstants.BOTTOM)
                paint = new GradientPaint(0, 0, background.darker(), 0, button.getHeight(), background.brighter());
            else
                paint = new GradientPaint(0, 0, background.darker(), button.getWidth(), 0, background.brighter());
            g2d.setPaint(paint);

            if (toFill) {
                g2d.fillRoundRect(3, 3, button.getWidth() - 6, button.getHeight() - 6, 5, 5);
            }

            if (toBorder) {
                g.setColor(Color.black);
                g.drawRoundRect(3, 3, button.getWidth() - 6, button.getHeight() - 6, 5, 5);
            }
        } else {
            if (toFill) {
                g.setColor(background);
                g.fillRoundRect(3, 3, button.getWidth() - 6, button.getHeight() - 6, 5, 5);
            }

            if (toBorder) {
                g.setColor(Color.gray);
                g.drawRoundRect(3, 3, button.getWidth() - 6, button.getHeight() - 6, 5, 5);
            }
        }

        if (model.isRollover()) {
            if (!model.isArmed() && !model.isPressed() && !model.isSelected()) {
                final Graphics2D g2d = (Graphics2D) g;
                final GradientPaint paint;
                if (anchor == SwingConstants.TOP || anchor == SwingConstants.BOTTOM)
                    paint = new GradientPaint(0, 0, background, 0, button.getHeight(), Color.white);
                else
                    paint = new GradientPaint(0, 0, background, button.getWidth(), 0, Color.white);
                g2d.setPaint(paint);
                g2d.fillRoundRect(3, 3, button.getWidth() - 6, button.getHeight() - 6, 5, 5);
            }

            if (toBorder) {
                g.setColor(Color.darkGray);
                g.drawRoundRect(3, 3, button.getWidth() - 6, button.getHeight() - 6, 5, 5);
            }
        }

        AffineTransform tr = null;

        if (anchor == SwingConstants.LEFT || anchor == SwingConstants.RIGHT) {
            tr = g2.getTransform();
            if (anchor == SwingConstants.RIGHT) {
                if (icon != null)
                    icon.paintIcon(c, g2, iconRect.y, iconRect.x);
                g2.rotate(Math.PI/2);
                g2.translate(0, -c.getWidth());
            } else {
                if (icon != null)
                    icon.paintIcon(c, g2, iconRect.y, c.getHeight() - iconRect.x - icon.getIconHeight());
                g2.rotate(-Math.PI/2);
                g2.translate(-c.getHeight(), 0);
            }
        } else {
            if (icon != null)
                icon.paintIcon(c, g2, iconRect.x, iconRect.y);
        }


        if (text != null) {
            if (model.isEnabled()) {
                if (model.isArmed() && model.isPressed() || model.isSelected())
                    g.setColor(background);
                else
                    g.setColor(button.getForeground());
            } else {
                g.setColor(background.darker());
            }

            if (model.isEnabled()) {
                g.setColor(button.getForeground());
                BasicGraphicsUtils.drawString(g, clippedText, button.getMnemonic(), textRect.x, textRect.y + fm.getAscent());
            } else {
                if (model.isSelected())
                    g.setColor(c.getBackground());
                else
                    g.setColor(getDisabledTextColor());
                BasicGraphicsUtils.drawString(g, clippedText, button.getMnemonic(), textRect.x, textRect.y + fm.getAscent());
            }
        }
        if (anchor == SwingConstants.RIGHT || anchor == SwingConstants.LEFT)
            g2.setTransform(tr);
    }
}